/*
 * Copyright (c) 2018 Hitevision
 */

package tw.com.hitevision.whiteboard.android.widgets;

import android.content.Context;
import android.content.res.Resources;
import android.os.Handler;
import android.util.AttributeSet;
import android.view.MotionEvent;
import android.view.View;
import android.widget.RelativeLayout;
import android.widget.TextView;

import tw.com.hitevision.whiteboard.android.Props;
import tw.com.hitevision.whiteboard.android.R;
import tw.com.hitevision.whiteboard.android.state.WordProperty;

public class WordMenuView extends RelativeLayout {
    private static final int SIZE_CHANGE_RATE = 300; // in ms

    private WordProperty.TextColor color;
    private float size;
    private OnChangeListener listener;
    private Handler handler;

    private View[] colors;
    private TextView sizeText;

    public WordMenuView(Context context) {
        super(context);
        init(context);
    }

    public WordMenuView(Context context, AttributeSet attrs) {
        super(context, attrs);
        init(context);
    }

    public WordMenuView(Context context, AttributeSet attrs, int defStyleAttr) {
        super(context, attrs, defStyleAttr);
        init(context);
    }

    private void init(Context context) {
        handler = new Handler();

        final Resources r = getResources();

        setBackgroundResource(R.drawable.ic_menu_bubble_text);

//        final int paddingTop = r.getDimensionPixelSize(R.dimen.word_menu_padding_top);
//        final int padding = r.getDimensionPixelSize(R.dimen.word_menu_padding);
//        setPadding(padding, paddingTop, padding, 0);

        inflate(context, R.layout.menu_word, this);

        View color1 = findViewById(R.id.color_1);
        color1.setOnClickListener(colorsOnClickListener);
        View color2 = findViewById(R.id.color_2);
        color2.setOnClickListener(colorsOnClickListener);
        View color3 = findViewById(R.id.color_3);
        color3.setOnClickListener(colorsOnClickListener);
        View color4 = findViewById(R.id.color_4);
        color4.setOnClickListener(colorsOnClickListener);
        View color5 = findViewById(R.id.color_5);
        color5.setOnClickListener(colorsOnClickListener);
        View color6 = findViewById(R.id.color_6);
        color6.setOnClickListener(colorsOnClickListener);
        View color7 = findViewById(R.id.color_7);
        color7.setOnClickListener(colorsOnClickListener);
        View color8 = findViewById(R.id.color_8);
        color8.setOnClickListener(colorsOnClickListener);
        View color9 = findViewById(R.id.color_9);
        color9.setOnClickListener(colorsOnClickListener);
        View color10 = findViewById(R.id.color_10);
        color10.setOnClickListener(colorsOnClickListener);
        View color11 = findViewById(R.id.color_11);
        color11.setOnClickListener(colorsOnClickListener);
        colors = new View[] {color1, color2, color3, color4, color5, color6, color7, color8, color9, color10, color11};

        View decrease = findViewById(R.id.decrease);
        decrease.setOnTouchListener(sizesOnTouchListener);
        View increase = findViewById(R.id.increase);
        increase.setOnTouchListener(sizesOnTouchListener);
        sizeText = findViewById(R.id.size);
    }

    private final OnClickListener colorsOnClickListener = v -> {
        for (View view : colors) {
            view.setSelected(false);
        }
        v.setSelected(true);

        if (Props.getFlavorModel().equals(Props.Flavor.Model.Oem)) {
            switch (v.getId()) {
                case R.id.color_1:
                    color = WordProperty.TextColor.WHITE;
                    break;
                case R.id.color_2:
                    color = WordProperty.TextColor.BLACK;
                    break;
                case R.id.color_3:
                    color = WordProperty.TextColor.RED;
                    break;
                case R.id.color_4:
                    color = WordProperty.TextColor.GREEN;
                    break;
                case R.id.color_5:
                    color = WordProperty.TextColor.BLUE;
                    break;
                case R.id.color_6:
                    color = WordProperty.TextColor.YELLOW;
                    break;
                case R.id.color_7:
                    color = WordProperty.TextColor.BLUE_SOFT;
                    break;
                case R.id.color_8:
                    color = WordProperty.TextColor.GREEN_SOFT;
                    break;
                case R.id.color_9:
                    color = WordProperty.TextColor.PINK;
                    break;
                case R.id.color_10:
                    color = WordProperty.TextColor.VERMILION;
                    break;
                case R.id.color_11:
                    color = WordProperty.TextColor.YELLOW_SOFT;
                    break;
            }
        } else {
            switch (v.getId()) {
                case R.id.color_1:
                    color = WordProperty.TextColor.BLACK;
                    break;
                case R.id.color_2:
                    color = WordProperty.TextColor.WHITE;
                    break;
                case R.id.color_3:
                    color = WordProperty.TextColor.RED;
                    break;
                case R.id.color_4:
                    color = WordProperty.TextColor.YELLOW;
                    break;
                case R.id.color_5:
                    color = WordProperty.TextColor.GREEN;
                    break;
                case R.id.color_6:
                    color = WordProperty.TextColor.BLUE;
                    break;
                case R.id.color_7:
                    color = WordProperty.TextColor.PURPLE;
                    break;
            }
        }

        if (listener != null) {
            listener.onSelectWordColor(0, color);
        }
    };

    private boolean isIncreasing;

    private final OnTouchListener sizesOnTouchListener = new OnTouchListener() {

        @Override
        public boolean onTouch(View v, MotionEvent event) {
            switch (event.getAction()) {
                case MotionEvent.ACTION_DOWN: {
                    isIncreasing = v.getId() == R.id.increase;
                    handler.removeCallbacks(changeSize);
                    handler.post(changeSize);
                    break;
                }
                case MotionEvent.ACTION_UP:
                case MotionEvent.ACTION_CANCEL: {
                    handler.removeCallbacks(changeSize);
                    break;
                }
            }
            return false;
        }
    };

    private final Runnable changeSize = new Runnable() {
        @Override
        public void run() {
            if (isIncreasing) {
                size += WordProperty.SIZE_INCREMENT;
            } else {
                size -= WordProperty.SIZE_INCREMENT;
            }

            if (size < 0) {
                size = 0;
            } else if (size < WordProperty.MIN_SIZE) {
                size = WordProperty.MIN_SIZE;
            } else if (size > WordProperty.MAX_SIZE) {
                size = WordProperty.MAX_SIZE;
            }

            sizeText.setText(Integer.toString((int) size));
            if (listener != null) {
                listener.onSelectWordSize(0, size);
            }

            if (size > WordProperty.MIN_SIZE && size < WordProperty.MAX_SIZE) {
                handler.postDelayed(changeSize, SIZE_CHANGE_RATE);
            }
        }
    };

    public void setColor(WordProperty.TextColor color) {
        if (color == null) {
            return;
        }

        this.color = color;

        int viewId = 0;
        if (Props.getFlavorModel().equals(Props.Flavor.Model.Oem)) {
            switch (color) {
                case WHITE:
                    viewId = R.id.color_1;
                    break;
                case BLACK:
                    viewId = R.id.color_2;
                    break;
                case RED:
                    viewId = R.id.color_3;
                    break;
                case GREEN:
                    viewId = R.id.color_4;
                    break;
                case BLUE:
                    viewId = R.id.color_5;
                    break;
                case YELLOW:
                    viewId = R.id.color_6;
                    break;
                case BLUE_SOFT:
                    viewId = R.id.color_7;
                    break;
                case GREEN_SOFT:
                    viewId = R.id.color_8;
                    break;
                case PINK:
                    viewId = R.id.color_9;
                    break;
                case VERMILION:
                    viewId = R.id.color_10;
                    break;
                case YELLOW_SOFT:
                    viewId = R.id.color_11;
                    break;
            }
        } else {
            switch (color) {
                case BLACK:
                    viewId = R.id.color_1;
                    break;
                case WHITE:
                    viewId = R.id.color_2;
                    break;
                case RED:
                    viewId = R.id.color_3;
                    break;
                case YELLOW:
                    viewId = R.id.color_4;
                    break;
                case GREEN:
                    viewId = R.id.color_5;
                    break;
                case BLUE:
                    viewId = R.id.color_6;
                    break;
                case PURPLE:
                    viewId = R.id.color_7;
                    break;
            }
        }

        for (View view : colors) {
            view.setSelected(view.getId() == viewId);
        }
    }

    public WordProperty.TextColor getColor() {
        return color;
    }

    public void setSize(float size) {
        this.size = size;
        sizeText.setText(Integer.toString((int) size));
    }

    public float getSize() {
        return size;
    }

    public void setOnChangeListener(OnChangeListener listener) {
        this.listener = listener;
    }

    public interface OnChangeListener {
        void onSelectWordColor(int pointer, WordProperty.TextColor color);

        void onSelectWordSize(int pointer, float size);
    }
}
